namespace YM {
    export enum UILayer {
        Base = 0,

    }
    export class UIRoot extends Entity{

    }
    export class UIBase extends Entity {
        protected _inited: boolean = false;
        public get inited(): boolean {
            return this._inited;
        }
        public init(): void {
            if(this.inited){
                return;
            }
            this._inited = true;
            let eventNames=this.onRegist();
            eventNames.forEach(eventName=>{
                game.event.registerEvent(eventName,this.onHandle,this);
            });
        }
        protected onRegist():string[] {
            let eventNames=new Array<string>();
            return eventNames;
        }
        protected onHandle(eventName: string, arg: any[]) {

        }
        public show(): void {
            
        }
        public hide(): void {

        }
        public async showAsync() {

        }
        public async hideAsync() {

        }
    }
    export class UIPanel<T extends fgui.GComponent> extends UIBase {
        content: T;
        private uipanelInfo:any[];
        protected awake(uiPanelInfo){
            this.uipanelInfo=uiPanelInfo;
        }
        public init(): void {
            if(this.uipanelInfo[1])
            this.content=this.uipanelInfo[1].createInstance();
            fgui.GRoot.inst.addChild(this.content);
            this.content.visible=false;
            super.init();
        }
        show():void{
            if(!this.inited){
                this.init();
            }
            this.content.visible=true;
        }
        hide():void{
            if(!this.inited){
                this.init();
            }
            this.content.visible=false;
        }
    }
    export class UIPanelWindow<T extends fgui.GComponent> extends UIBase {
        content: T;
        public CloseEvent:Function;
        protected panelWindow:fgui.GComponent;
        private uipanelInfo:any[];
        protected awake(uiPanelInfo){
            this.uipanelInfo=uiPanelInfo;
        }
        public init(): void {
            if(this.uipanelInfo[1])
            this.content=this.uipanelInfo[1].createInstance();
            fgui.GRoot.inst.addChild(this.content);
            this.content.visible=false;
            super.init();
            this.panelWindow=this.content.getChild("window").asCom;
            let btnClose=this.panelWindow.getChild("btn_close");
            if(btnClose)
            btnClose.asButton.onClick(()=>{
                if(this.CloseEvent)this.CloseEvent();
                this.hide();
            },this);
        }
        show():void{
            if(!this.inited){
                this.init();
            }
            this.content.visible=true;
            fgui.GTween
            .to(0,1,0.35)
            .setTarget(this,(x)=>{this.panelWindow.setScale(x,x)})
            .setEase(fgui.EaseType.BounceOut);
        }
        hide():void{
            if(!this.inited){
                this.init();
            }
            this.content.visible=false;
        }
    }
    export class UIMgr {
        public Root:UIRoot;
        public UICamera:cc.Camera;
        private uiDic: Map<{ new() }, UIBase> = new Map<{ new(): UIBase }, UIBase>();
        private uiStack: UIBase[] = [];
        public init() {
            fgui.GRoot.create();
            cc.game.addPersistRootNode(fgui.GRoot.inst.node);
            
            let cam=new cc.Node("UICamera");
            cam.addComponent(cc.Camera).cullingMask=1<<1;
            cam.getComponent(cc.Camera).depth=0;
            cam.x=fgui.GRoot.inst.width/2;
            cam.y=fgui.GRoot.inst.height/2;
            cc.game.addPersistRootNode(cam);
            this.UICamera=cam.getComponent(cc.Camera);

            fgui.addLoadHandler();
            //Laya.stage.addChild(fgui.GRoot.inst.displayObject);
            this.Root=EntityFactory.create(UIRoot,null);
            
            for (const uipanelInfo of uiPanels) {
                if(uipanelInfo[2])
                uipanelInfo[2].bindAll();
                let panel= EntityFactory.createWithParent(uipanelInfo[0],this.Root,uipanelInfo);
                this.uiDic.set(uipanelInfo[0],panel as UIBase);
            }
        }
        public async loadPackage(packgeInfo:packageInfo){
            if(fgui.UIPackage.getByName(packgeInfo.name)){
                YM.log(packgeInfo.path+"/"+packgeInfo.name,"已经存在");
                return;
            }
            let resInfo=new Array<string>();
            resInfo.push(packgeInfo.path+"/"+packgeInfo.name+"."+"bin");
            if(packgeInfo.altasInfos){
                packgeInfo.altasInfos.forEach((value:altasInfo)=>{
                    for (let i = 0; i < value.count; i++) { 
                        if(i!=0){
                            resInfo.push(packgeInfo.path+"/"+packgeInfo.name+"_atlas"+value.id+"_"+i+value.format);
                        }
                        else{
                            resInfo.push(packgeInfo.path+"/"+packgeInfo.name+"_atlas"+value.id+value.format);
                        }
                    }
                })
            }
            await game.res.loadArrAsync(resInfo);
            this.addPackage(packgeInfo.path+"/"+packgeInfo.name);
        }
        public addPackage(packageName: string) {
            fgui.UIPackage.addPackage(packageName);
        }
        public removePackage(packageName:string){
            fgui.UIPackage.removePackage(packageName);
        }
        public get<T extends UIBase>(type: { new(): T }): T {
            let ui = this.uiDic.get(type);
            return ui as T;
        }
        public show<T extends UIBase>(type: { new(): T }): T {
            let ui = this.uiDic.get(type);
            ui.show();
            return ui as T;
        }
        public hide<T extends UIBase>(type: { new(): T }): T {
            let ui = this.uiDic.get(type);
            ui.hide();
            return ui as T;
        }
        public hideAll(){
            for (const ui of this.uiDic) {
                if(ui[1].inited){
                    ui[1].hide();
                }
            }
        }
        public hideAllWindow(){
            for (const ui of this.uiDic) {
                if(ui[1].inited&&ui[1] instanceof UIPanelWindow){
                    ui[1].hide();
                }
            }
        }
        public async showAsync<T extends UIBase>(type: { new(): T }) {
            let ui = this.uiDic.get(type);
            if (!ui.inited) {
                ui.init();
            }
            await ui.showAsync();
            return ui as T;
        }
        public async hideAsync<T extends UIBase>(type: { new(): T }) {
            let ui = this.uiDic.get(type);
            if (!ui.inited) {
                ui.init();
            }
            await ui.hideAsync();
            return ui as T;
        }
    }
    export class packageInfo{
        name:string;
        path:string;
        altasInfos:altasInfo[];
        constructor(name:string,path:string,altasInfos?:altasInfo[]){
            this.name=name;
            this.path=path;
            this.altasInfos=altasInfos;
        }
    }
    export class altasInfo{
        id:number;
        count:number;
        format:string;
        constructor(id:number=0,count:number=1,format=".png"){
            this.id=id;
            this.count=count;
            this.format=format;
        }
    }
}